/*     */ package com.zimbra.cs.service;
/*     */ 
/*     */ import com.google.common.base.Charsets;
/*     */ import com.google.common.base.Objects;
/*     */ import com.google.common.base.Objects.ToStringHelper;
/*     */ import com.zimbra.common.account.Key.AccountBy;
/*     */ import com.zimbra.common.mime.ContentDisposition;
/*     */ import com.zimbra.common.mime.ContentType;
/*     */ import com.zimbra.common.service.ServiceException;
/*     */ import com.zimbra.common.util.ByteUtil;
/*     */ import com.zimbra.common.util.DateUtil;
/*     */ import com.zimbra.common.util.HttpUtil;
/*     */ import com.zimbra.common.util.L10nUtil;
/*     */ import com.zimbra.common.util.L10nUtil.MsgKey;
/*     */ import com.zimbra.common.util.Log;
/*     */ import com.zimbra.common.util.StringUtil;
/*     */ import com.zimbra.common.util.ZimbraLog;
/*     */ import com.zimbra.cs.account.Account;
/*     */ import com.zimbra.cs.account.AuthToken;
/*     */ import com.zimbra.cs.account.Config;
/*     */ import com.zimbra.cs.account.GuestAccount;
/*     */ import com.zimbra.cs.account.Provisioning;
/*     */ import com.zimbra.cs.account.Server;
/*     */ import com.zimbra.cs.index.SortBy;
/*     */ import com.zimbra.cs.mailbox.MailItem;
/*     */ import com.zimbra.cs.mailbox.Mailbox;
/*     */ import com.zimbra.cs.mailbox.OperationContext;
/*     */ import com.zimbra.cs.service.formatter.Formatter;
/*     */ import com.zimbra.cs.service.formatter.FormatterFactory.FormatType;
/*     */ import com.zimbra.cs.service.util.ItemId;
/*     */ import com.zimbra.cs.servlet.util.CsrfUtil;
/*     */ import java.io.IOException;
/*     */ import java.io.InputStream;
/*     */ import java.nio.charset.Charset;
/*     */ import java.util.ArrayList;
/*     */ import java.util.Iterator;
/*     */ import java.util.Locale;
/*     */ import java.util.Map;
/*     */ import java.util.zip.GZIPInputStream;
/*     */ import javax.servlet.http.HttpServletRequest;
/*     */ import javax.servlet.http.HttpServletResponse;
/*     */ import org.apache.commons.fileupload.FileItem;
/*     */ import org.apache.commons.fileupload.FileItemIterator;
/*     */ import org.apache.commons.fileupload.FileItemStream;
/*     */ import org.apache.commons.fileupload.servlet.ServletFileUpload;
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ public class UserServletContext
/*     */ {
/*     */   public final HttpServletRequest req;
/*     */   public final HttpServletResponse resp;
/*     */   public final UserServlet servlet;
/*     */   public final Map<String, String> params;
/*     */   public FormatterFactory.FormatType format;
/*     */   public Formatter formatter;
/*     */   public boolean cookieAuthHappened;
/*     */   public boolean basicAuthHappened;
/*     */   public boolean qpAuthHappened;
/*     */   public String accountPath;
/*     */   public AuthToken authToken;
/*     */   public String itemPath;
/*     */   public String extraPath;
/*     */   public ItemId itemId;
/*     */   public MailItem target;
/*     */   public SortBy sortBy;
/*  82 */   public FakeFolder fakeTarget = null;
/*     */   public int[] reqListIds;
/*     */   public ArrayList<Item> requestedItems;
/*     */   public boolean fromDumpster;
/*  86 */   public boolean wantCustomHeaders = true;
/*  87 */   public int imapId = -1;
/*     */   public boolean sync;
/*     */   private Account authAccount;
/*     */   public Account targetAccount;
/*     */   public Mailbox targetMailbox;
/*     */   public OperationContext opContext;
/*     */   private Locale locale;
/*  94 */   private long mStartTime = -2L;
/*  95 */   private long mEndTime = -2L;
/*     */   
/*     */   private Throwable error;
/*     */   
/*     */   private boolean csrfAuthSucceeded;
/*     */   
/*     */   private static final long DEFAULT_MAX_POST_SIZE = 10485760L;
/*     */   
/*     */   public boolean isCsrfAuthSucceeded()
/*     */   {
/* 105 */     return this.csrfAuthSucceeded;
/*     */   }
/*     */   
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/* 113 */   public void setCsrfAuthSucceeded(boolean csrfAuthSucceeded) { this.csrfAuthSucceeded = csrfAuthSucceeded; }
/*     */   
/*     */   public static class Item {
/*     */     public int id;
/*     */     public String acctId;
/*     */     public int ver;
/*     */     public boolean versioned;
/*     */     public MailItem mailItem;
/*     */     
/*     */     public Item(String itemId, Account targetAccount) throws ServiceException {
/* 123 */       String[] vals = itemId.split("\\.");
/* 124 */       ItemId iid = new ItemId(vals.length > 0 ? vals[0] : itemId, targetAccount == null ? (String)null : targetAccount.getId());
/* 125 */       this.id = iid.getId();
/* 126 */       if ((targetAccount != null) && (!targetAccount.getId().equals(iid.getAccountId()))) {
/* 127 */         this.acctId = iid.getAccountId();
/*     */       }
/* 129 */       if (vals.length == 2) {
/* 130 */         this.versioned = true;
/* 131 */         this.ver = Integer.parseInt(vals[1]);
/*     */       }
/*     */     }
/*     */   }
/*     */   
/*     */   private static class ItemIterator implements Iterator<MailItem>
/*     */   {
/*     */     private final Iterator<UserServletContext.Item> items;
/*     */     
/*     */     public ItemIterator(ArrayList<UserServletContext.Item> items) {
/* 141 */       this.items = items.iterator();
/*     */     }
/*     */     
/*     */     public boolean hasNext()
/*     */     {
/* 146 */       return this.items.hasNext();
/*     */     }
/*     */     
/*     */     public MailItem next()
/*     */     {
/* 151 */       return ((UserServletContext.Item)this.items.next()).mailItem;
/*     */     }
/*     */     
/*     */     public void remove() {}
/*     */   }
/*     */   
/*     */   public static class FakeFolder
/*     */   {
/*     */     private final String account;
/*     */     private final String path;
/*     */     private final String name;
/*     */     
/*     */     public FakeFolder(String targetAccount, String calPath, String calName) {
/* 164 */       this.account = targetAccount;
/* 165 */       this.path = calPath;
/* 166 */       this.name = calName; }
/*     */     
/* 168 */     public String getAccount() { return this.account; }
/* 169 */     public String getPath() { return this.path; }
/* 170 */     public String getName() { return this.name; }
/*     */   }
/*     */   
/*     */   public UserServletContext(HttpServletRequest request, HttpServletResponse response, UserServlet srvlt) throws UserServletException, ServiceException
/*     */   {
/* 175 */     this.req = request;
/* 176 */     this.resp = response;
/* 177 */     this.servlet = srvlt;
/* 178 */     this.params = HttpUtil.getURIParams(request);
/* 179 */     this.sortBy = getSortBy();
/*     */     
/*     */ 
/* 182 */     String language = (String)this.params.get("language");
/* 183 */     if (language != null) {
/* 184 */       String country = (String)this.params.get("country");
/* 185 */       if (country != null) {
/* 186 */         String variant = (String)this.params.get("variant");
/* 187 */         if (variant != null) {
/* 188 */           this.locale = new Locale(language, country, variant);
/*     */         } else {
/* 190 */           this.locale = new Locale(language, country);
/*     */         }
/*     */       } else {
/* 193 */         this.locale = new Locale(language);
/*     */       }
/*     */     }
/*     */     
/* 197 */     parseParams(request, this.authToken);
/*     */   }
/*     */   
/*     */   protected void parseParams(HttpServletRequest request, AuthToken authToken) throws UserServletException, ServiceException
/*     */   {
/* 202 */     Provisioning prov = Provisioning.getInstance();
/*     */     
/* 204 */     String pathInfo = request.getPathInfo();
/* 205 */     if ((pathInfo == null) || (pathInfo.equals("/")) || (pathInfo.equals("")) || (!pathInfo.startsWith("/")))
/* 206 */       throw new UserServletException(400, L10nUtil.getMessage(L10nUtil.MsgKey.errInvalidPath, request, new Object[0]));
/* 207 */     int pos = pathInfo.indexOf('/', 1);
/* 208 */     if (pos == -1)
/* 209 */       pos = pathInfo.length();
/* 210 */     if (pos < 1) {
/* 211 */       throw new UserServletException(400, L10nUtil.getMessage(L10nUtil.MsgKey.errInvalidPath, request, new Object[0]));
/*     */     }
/* 213 */     this.accountPath = pathInfo.substring(1, pos).toLowerCase();
/*     */     
/* 215 */     if (pos < pathInfo.length()) {
/* 216 */       this.itemPath = pathInfo.substring(pos + 1);
/* 217 */       if (this.itemPath.equals(""))
/* 218 */         this.itemPath = "/";
/*     */     } else {
/* 220 */       this.itemPath = "/";
/*     */     }
/* 222 */     this.extraPath = ((String)this.params.get("name"));
/* 223 */     this.format = FormatterFactory.FormatType.fromString((String)this.params.get("fmt"));
/* 224 */     String id = (String)this.params.get("id");
/*     */     try {
/* 226 */       this.itemId = (id == null ? null : new ItemId(id, (String)null));
/*     */     } catch (ServiceException e) {
/* 228 */       throw new UserServletException(400, L10nUtil.getMessage(L10nUtil.MsgKey.errInvalidId, request, new Object[0]));
/*     */     }
/*     */     
/* 231 */     String imap = (String)this.params.get("imap_id");
/*     */     try {
/* 233 */       this.imapId = (imap == null ? -1 : Integer.parseInt(imap));
/*     */     } catch (NumberFormatException nfe) {
/* 235 */       throw new UserServletException(400, L10nUtil.getMessage(L10nUtil.MsgKey.errInvalidImapId, request, new Object[0]));
/*     */     }
/*     */     
/* 238 */     if (this.format != null) {
/* 239 */       this.formatter = UserServlet.getFormatter(this.format);
/* 240 */       if (this.formatter == null) {
/* 241 */         throw new UserServletException(501, L10nUtil.getMessage(L10nUtil.MsgKey.errNotImplemented, request, new Object[0]));
/*     */       }
/* 243 */       this.formatter.validateParams(this);
/*     */     }
/*     */     
/*     */ 
/*     */ 
/* 248 */     if ((this.itemId != null) && (this.itemId.getAccountId() != null)) {
/* 249 */       this.targetAccount = prov.get(Key.AccountBy.id, this.itemId.getAccountId(), authToken);
/* 250 */     } else if (!this.accountPath.equals("~"))
/*     */     {
/*     */ 
/* 253 */       if (this.accountPath.startsWith("~")) {
/* 254 */         this.accountPath = this.accountPath.substring(1);
/*     */       }
/* 256 */       this.targetAccount = prov.get(Key.AccountBy.name, this.accountPath, authToken);
/*     */     }
/*     */     
/* 259 */     String listParam = (String)this.params.get("list");
/* 260 */     if ((listParam != null) && (listParam.length() > 0)) {
/* 261 */       String[] ids = listParam.split(",");
/* 262 */       this.requestedItems = new ArrayList();
/* 263 */       this.reqListIds = new int[ids.length];
/* 264 */       String proxyAcct = null;
/* 265 */       for (int i = 0; i < ids.length; i++) {
/* 266 */         Item item = new Item(ids[i], this.targetAccount);
/* 267 */         this.requestedItems.add(item);
/* 268 */         this.reqListIds[i] = item.id;
/* 269 */         if ((this.targetAccount != null) && (!this.targetAccount.getId().equals(item.acctId))) {
/* 270 */           if ((proxyAcct != null) && (!proxyAcct.equals(item.acctId)))
/* 271 */             throw ServiceException.INVALID_REQUEST("Cross account multi list is not supported. already requested item from " + proxyAcct + " also found " + item.acctId + ":" + item.id, null);
/* 272 */           if (proxyAcct == null) {
/* 273 */             proxyAcct = item.acctId;
/*     */           }
/*     */         }
/*     */       }
/* 277 */       if (proxyAcct != null) {
/* 278 */         this.targetAccount = prov.get(Key.AccountBy.id, proxyAcct, authToken);
/*     */       }
/*     */     }
/*     */     
/* 282 */     String dumpsterParam = (String)this.params.get("dumpster");
/* 283 */     this.fromDumpster = ((dumpsterParam != null) && (!dumpsterParam.equals("0")) && (!dumpsterParam.equalsIgnoreCase("false")));
/*     */   }
/*     */   
/*     */   public Locale getLocale() {
/* 287 */     return this.locale != null ? this.locale : this.req.getLocale();
/*     */   }
/*     */   
/*     */   public void setAuthAccount(Account value) throws ServiceException {
/* 291 */     this.authAccount = value;
/* 292 */     if ((this.locale == null) && (this.authAccount != null) && (this.authAccount.getLocale() != null)) {
/* 293 */       this.locale = this.authAccount.getLocale();
/*     */     }
/*     */   }
/*     */   
/*     */   public Account getAuthAccount() {
/* 298 */     return this.authAccount;
/*     */   }
/*     */   
/*     */   public Iterator<MailItem> getRequestedItems() {
/* 302 */     return new ItemIterator(this.requestedItems);
/*     */   }
/*     */   
/*     */   public boolean isUsingAdminPrivileges() {
/* 306 */     return (this.authToken != null) && (AuthToken.isAnyAdmin(this.authToken));
/*     */   }
/*     */   
/*     */   public UserServlet getServlet() {
/* 310 */     return this.servlet;
/*     */   }
/*     */   
/*     */   public long getStartTime() {
/* 314 */     if (this.mStartTime == -2L) {
/* 315 */       String st = (String)this.params.get("start");
/* 316 */       long defaultStartTime = this.formatter.getDefaultStartTime();
/* 317 */       this.mStartTime = (st != null ? DateUtil.parseDateSpecifier(st, defaultStartTime) : defaultStartTime);
/*     */     }
/* 319 */     return this.mStartTime;
/*     */   }
/*     */   
/*     */   public long getEndTime() {
/* 323 */     if (this.mEndTime == -2L) {
/* 324 */       String et = (String)this.params.get("end");
/* 325 */       long defaultEndTime = this.formatter.getDefaultEndTime();
/* 326 */       this.mEndTime = (et != null ? DateUtil.parseDateSpecifier(et, defaultEndTime) : defaultEndTime);
/*     */     }
/* 328 */     return this.mEndTime;
/*     */   }
/*     */   
/*     */   public int getFreeBusyCalendar() {
/* 332 */     int folder = -1;
/* 333 */     String str = (String)this.params.get("fbcal");
/* 334 */     if (str != null) {
/*     */       try {
/* 336 */         folder = Integer.parseInt(str);
/*     */       } catch (NumberFormatException e) {}
/*     */     }
/* 339 */     return folder;
/*     */   }
/*     */   
/*     */   public boolean ignoreAndContinueOnError() {
/* 343 */     String val = (String)this.params.get("ignore");
/* 344 */     if (val != null) {
/*     */       try {
/* 346 */         int n = Integer.parseInt(val);
/* 347 */         return n != 0;
/*     */       } catch (NumberFormatException e) {}
/*     */     }
/* 350 */     return false;
/*     */   }
/*     */   
/*     */   public boolean preserveAlarms() {
/* 354 */     String val = (String)this.params.get("preserveAlarms");
/* 355 */     if (val != null) {
/*     */       try {
/* 357 */         int n = Integer.parseInt(val);
/* 358 */         return n != 0;
/*     */       } catch (NumberFormatException e) {}
/*     */     }
/* 361 */     return false;
/*     */   }
/*     */   
/*     */   public boolean noHierarchy() {
/* 365 */     String val = (String)this.params.get("nohierarchy");
/* 366 */     if (val != null) {
/*     */       try {
/* 368 */         int n = Integer.parseInt(val);
/* 369 */         return n != 0;
/*     */       } catch (NumberFormatException e) {}
/*     */     }
/* 372 */     return false;
/*     */   }
/*     */   
/*     */   public String getQueryString() {
/* 376 */     return (String)this.params.get("query");
/*     */   }
/*     */   
/*     */   private SortBy getSortBy() throws UserServletException {
/* 380 */     String sort = (String)this.params.get("sort");
/* 381 */     if (sort == null) {
/* 382 */       return SortBy.DATE_DESC;
/*     */     }
/* 384 */     SortBy sortBy = SortBy.of(sort);
/* 385 */     if (sortBy == null) {
/* 386 */       throw UserServletException.badRequest(sort + " is not a valid sort order");
/*     */     }
/* 388 */     return sortBy;
/*     */   }
/*     */   
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */ 
/*     */   public Charset getCharset()
/*     */     throws ServiceException
/*     */   {
/* 400 */     String charset = (String)this.params.get("charset");
/* 401 */     if (charset != null) {
/*     */       try {
/* 403 */         return Charset.forName(charset);
/*     */       } catch (IllegalArgumentException e) {
/* 405 */         throw ServiceException.INVALID_REQUEST("invalid charset: " + charset, e);
/*     */       }
/*     */     }
/* 408 */     return Charsets.UTF_8;
/*     */   }
/*     */   
/*     */   public boolean cookieAuthAllowed()
/*     */   {
/* 413 */     return getAuth().indexOf("co") != -1;
/*     */   }
/*     */   
/*     */   public boolean isAuthedAcctGuest() {
/* 417 */     return (this.authAccount != null) && ((this.authAccount instanceof GuestAccount));
/*     */   }
/*     */   
/*     */   public boolean setCookie()
/*     */   {
/* 422 */     return (!isAuthedAcctGuest()) && (getAuth().indexOf("sc") != -1) && (getAuth().indexOf("nsc") == -1);
/*     */   }
/*     */   
/*     */ 
/*     */   public boolean basicAuthAllowed()
/*     */   {
/* 428 */     String auth = getAuth();
/* 429 */     return (auth.indexOf("nsc") != -1) || (auth.indexOf("ba") != -1) || (auth.indexOf("sc") != -1);
/*     */   }
/*     */   
/*     */ 
/*     */   public boolean queryParamAuthAllowed()
/*     */   {
/* 435 */     return getAuth().indexOf("qp") != -1;
/*     */   }
/*     */   
/*     */   public String getAuth() {
/* 439 */     String a = (String)this.params.get("auth");
/* 440 */     return (a == null) || (a.length() == 0) ? "co,nsc,qp" : a;
/*     */   }
/*     */   
/*     */   public boolean hasPart() {
/* 444 */     String p = getPart();
/* 445 */     return (p != null) && (p.length() > 0);
/*     */   }
/*     */   
/*     */   public String getPart() {
/* 449 */     return (String)this.params.get("part");
/*     */   }
/*     */   
/*     */   public boolean hasBody() {
/* 453 */     String p = getBody();
/* 454 */     return p != null;
/*     */   }
/*     */   
/*     */   public String getBody() {
/* 458 */     return (String)this.params.get("body");
/*     */   }
/*     */   
/*     */   public boolean hasView() {
/* 462 */     String v = getView();
/* 463 */     return (v != null) && (v.length() > 0);
/*     */   }
/*     */   
/*     */   public String getView() {
/* 467 */     return (String)this.params.get("view");
/*     */   }
/*     */   
/*     */   public int getOffset() {
/* 471 */     String s = (String)this.params.get("offset");
/* 472 */     if (s != null) {
/* 473 */       int offset = Integer.parseInt(s);
/* 474 */       if (offset > 0)
/* 475 */         return offset;
/*     */     }
/* 477 */     return 0;
/*     */   }
/*     */   
/*     */   public int getLimit() {
/* 481 */     String s = (String)this.params.get("limit");
/* 482 */     if (s != null) {
/* 483 */       int limit = Integer.parseInt(s);
/* 484 */       if (limit > 0)
/* 485 */         return limit;
/*     */     }
/* 487 */     return 50;
/*     */   }
/*     */   
/*     */   public String getTypesString() {
/* 491 */     return (String)this.params.get("types");
/*     */   }
/*     */   
/*     */ 
/*     */   public boolean shouldReturnBody()
/*     */   {
/* 497 */     String bodyVal = (String)this.params.get("body");
/* 498 */     if ((bodyVal != null) && (bodyVal.equals("0")))
/* 499 */       return false;
/* 500 */     return true;
/*     */   }
/*     */   
/*     */   public void setAnonymousRequest() {
/* 504 */     this.authAccount = GuestAccount.ANONYMOUS_ACCT;
/*     */   }
/*     */   
/*     */   public boolean isAnonymousRequest() {
/* 508 */     return this.authAccount.equals(GuestAccount.ANONYMOUS_ACCT);
/*     */   }
/*     */   
/*     */   public boolean hasMaxWidth() {
/* 512 */     return getMaxWidth() != null;
/*     */   }
/*     */   
/*     */ 
/*     */ 
/*     */ 
/*     */   public Integer getMaxWidth()
/*     */   {
/* 520 */     String s = (String)this.params.get("max_width");
/* 521 */     if (StringUtil.isNullOrEmpty(s)) {
/* 522 */       return null;
/*     */     }
/*     */     try {
/* 525 */       return Integer.valueOf(Integer.parseInt(s));
/*     */     } catch (NumberFormatException e) {
/* 527 */       UserServlet.log.warn("Ignoring invalid maxWidth value: " + s); }
/* 528 */     return null;
/*     */   }
/*     */   
/*     */   public boolean hasMaxHeight()
/*     */   {
/* 533 */     return getMaxHeight() != null;
/*     */   }
/*     */   
/*     */ 
/*     */ 
/*     */ 
/*     */   public Integer getMaxHeight()
/*     */   {
/* 541 */     String s = (String)this.params.get("max_height");
/* 542 */     if (StringUtil.isNullOrEmpty(s)) {
/* 543 */       return null;
/*     */     }
/*     */     try {
/* 546 */       return Integer.valueOf(Integer.parseInt(s));
/*     */     } catch (NumberFormatException e) {
/* 548 */       UserServlet.log.warn("Ignoring invalid maxHeight value: " + s); }
/* 549 */     return null;
/*     */   }
/*     */   
/*     */ 
/*     */ 
/*     */ 
/*     */   public byte[] getPostBody()
/*     */     throws ServiceException, IOException, UserServletException
/*     */   {
/* 558 */     long sizeLimit = Provisioning.getInstance().getLocalServer().getLongAttr("zimbraFileUploadMaxSize", 10485760L);
/*     */     
/* 560 */     InputStream is = getRequestInputStream(sizeLimit);
/*     */     try {
/* 562 */       return ByteUtil.getContent(is, this.req.getContentLength(), sizeLimit);
/*     */     } finally {
/* 564 */       is.close();
/*     */     }
/*     */   }
/*     */   
/*     */   private static final class UploadInputStream extends InputStream {
/* 569 */     private FileItem fi = null;
/*     */     private final InputStream is;
/* 571 */     private long curSize = 0L;
/*     */     private final long maxSize;
/* 573 */     private long markSize = 0L;
/*     */     
/*     */     UploadInputStream(InputStream is, long maxSize) {
/* 576 */       this.is = is;
/* 577 */       this.maxSize = maxSize;
/*     */     }
/*     */     
/*     */     public void close() throws IOException {
/*     */       try {
/* 582 */         this.is.close();
/*     */       } finally {
/* 584 */         if (this.fi != null)
/* 585 */           this.fi.delete();
/* 586 */         this.fi = null;
/*     */       }
/*     */     }
/*     */     
/* 590 */     public int available() throws IOException { return this.is.available(); }
/*     */     
/* 592 */     public void mark(int where) { this.is.mark(where);this.markSize = this.curSize; }
/*     */     
/* 594 */     public boolean markSupported() { return this.is.markSupported(); }
/*     */     
/*     */     public int read() throws IOException
/*     */     {
/* 598 */       int value = this.is.read();
/* 599 */       if (value != -1)
/* 600 */         check(1L);
/* 601 */       return value;
/*     */     }
/*     */     
/* 604 */     public int read(byte[] b) throws IOException { return (int)check(this.is.read(b)); }
/*     */     
/*     */ 
/* 607 */     public int read(byte[] b, int off, int len) throws IOException { return (int)check(this.is.read(b, off, len)); }
/*     */     
/*     */     public void reset() throws IOException {
/* 610 */       this.is.reset();this.curSize = this.markSize; }
/*     */     
/* 612 */     public long skip(long n) throws IOException { return check(this.is.skip(n)); }
/*     */     
/*     */     private long check(long in) throws IOException {
/* 615 */       if (in > 0L) {
/* 616 */         this.curSize += in;
/* 617 */         if ((this.maxSize > 0L) && (this.curSize > this.maxSize))
/* 618 */           throw new IOException("upload over " + this.maxSize + " byte limit");
/*     */       }
/* 620 */       return in;
/*     */     }
/*     */   }
/*     */   
/*     */   public InputStream getRequestInputStream() throws IOException, ServiceException, UserServletException
/*     */   {
/* 626 */     return getRequestInputStream(0L);
/*     */   }
/*     */   
/*     */   public InputStream getRequestInputStream(long limit) throws IOException, ServiceException, UserServletException
/*     */   {
/* 631 */     String contentType = "application/octet-stream";
/* 632 */     String filename = null;
/* 633 */     InputStream is = null;
/* 634 */     long DEFAULT_MAX_SIZE = 10485760L;
/*     */     
/* 636 */     if (limit == 0L) {
/* 637 */       if (this.req.getParameter("lbfums") != null) {
/* 638 */         limit = Provisioning.getInstance().getLocalServer().getLongAttr("zimbraFileUploadMaxSize", 10485760L);
/*     */       }
/*     */       else {
/* 641 */         limit = Provisioning.getInstance().getConfig().getLongAttr("zimbraMtaMaxMessageSize", 10485760L);
/*     */       }
/*     */     }
/*     */     
/*     */ 
/* 646 */     boolean doCsrfCheck = false;
/* 647 */     if (this.req.getAttribute("CsrfTokenCheck") != null) {
/* 648 */       doCsrfCheck = ((Boolean)this.req.getAttribute("CsrfTokenCheck")).booleanValue();
/*     */     }
/*     */     
/*     */ 
/* 652 */     if (ServletFileUpload.isMultipartContent(this.req)) {
/* 653 */       ServletFileUpload sfu = new ServletFileUpload();
/*     */       try
/*     */       {
/* 656 */         FileItemIterator iter = sfu.getItemIterator(this.req);
/*     */         
/* 658 */         while (iter.hasNext()) {
/* 659 */           FileItemStream fis = iter.next();
/*     */           
/* 661 */           if (fis.isFormField()) {
/* 662 */             is = fis.openStream();
/* 663 */             this.params.put(fis.getFieldName(), new String(ByteUtil.getContent(is, -1), "UTF-8"));
/*     */             
/* 665 */             if ((doCsrfCheck) && (!this.csrfAuthSucceeded)) {
/* 666 */               String csrfToken = (String)this.params.get("csrfToken");
/* 667 */               if (UserServlet.log.isDebugEnabled()) {
/* 668 */                 String paramValue = this.req.getParameter("auth");
/* 669 */                 UserServlet.log.debug("CSRF check is: %s, CSRF token is: %s, Authentication recd with request is: %s", new Object[] { Boolean.valueOf(doCsrfCheck), csrfToken, paramValue });
/*     */               }
/*     */               
/*     */ 
/*     */ 
/* 674 */               if (!CsrfUtil.isValidCsrfToken(csrfToken, this.authToken)) {
/* 675 */                 setCsrfAuthSucceeded(Boolean.FALSE.booleanValue());
/* 676 */                 UserServlet.log.debug("CSRF token validation failed for account: %s, Auth token is CSRF enabled:  %sCSRF token is: %s", new Object[] { this.authToken, Boolean.valueOf(this.authToken.isCsrfTokenEnabled()), csrfToken });
/*     */                 
/*     */ 
/* 679 */                 throw new UserServletException(401, L10nUtil.getMessage(L10nUtil.MsgKey.errMustAuthenticate, new Object[0]));
/*     */               }
/*     */               
/* 682 */               setCsrfAuthSucceeded(Boolean.TRUE.booleanValue());
/*     */             }
/*     */             
/*     */ 
/*     */ 
/* 687 */             is.close();
/* 688 */             is = null;
/*     */           } else {
/* 690 */             is = new UploadInputStream(fis.openStream(), limit);
/* 691 */             break;
/*     */           }
/*     */         }
/*     */       } catch (UserServletException e) {
/* 695 */         throw new UserServletException(e.getHttpStatusCode(), e.getMessage(), e);
/*     */       } catch (Exception e) {
/* 697 */         throw new UserServletException(415, e.toString());
/*     */       }
/* 699 */       if (is == null)
/* 700 */         throw new UserServletException(204, "No file content");
/*     */     } else {
/* 702 */       ContentType ctype = new ContentType(this.req.getContentType());
/* 703 */       String contentEncoding = this.req.getHeader("Content-Encoding");
/*     */       
/* 705 */       contentType = ctype.getContentType();
/* 706 */       filename = ctype.getParameter("name");
/* 707 */       if ((filename == null) || (filename.trim().equals("")))
/* 708 */         filename = new ContentDisposition(this.req.getHeader("Content-Disposition")).getParameter("filename");
/* 709 */       is = new UploadInputStream((contentEncoding != null) && (contentEncoding.indexOf("gzip") != -1) ? new GZIPInputStream(this.req.getInputStream()) : this.req.getInputStream(), limit);
/*     */     }
/*     */     
/*     */ 
/*     */ 
/* 714 */     if ((filename == null) || (filename.trim().equals(""))) {
/* 715 */       filename = "unknown";
/*     */     } else
/* 717 */       this.params.put("uploadName", filename);
/* 718 */     this.params.put("uploadType", contentType);
/* 719 */     ZimbraLog.mailbox.info("UserServlet received file %s - %d request bytes", new Object[] { filename, Integer.valueOf(this.req.getContentLength()) });
/*     */     
/* 721 */     return is;
/*     */   }
/*     */   
/*     */   public void logError(Throwable e) {
/* 725 */     this.error = e;
/*     */   }
/*     */   
/*     */   public Throwable getLoggedError() {
/* 729 */     return this.error;
/*     */   }
/*     */   
/*     */   public String toString()
/*     */   {
/* 734 */     return Objects.toStringHelper(this).add("account", this.accountPath).add("item", this.itemPath).add("format", this.format).add("locale", this.locale).add("extraPath", this.extraPath).add("itemId", this.itemId).add("target", this.target).add("authAccount", this.authAccount).add("targetAccount", this.targetAccount).add("targetMailbox", this.targetMailbox).add("params", this.params).toString();
/*     */   }
/*     */ }


/* Location:              /home/mint/zimbrastore.jar!/com/zimbra/cs/service/UserServletContext.class
 * Java compiler version: 7 (51.0)
 * JD-Core Version:       0.7.1
 */